Completely replace URL handling with a sane, unified (if somewhat boring)
authorrobertlipe <robertlipe@f51c46e8-681c-474f-0cfe-069cfd0219fb>
Wed, 7 Aug 2013 16:59:40 +0000 (16:59 +0000)
committerrobertlipe <robertlipe@f51c46e8-681c-474f-0cfe-069cfd0219fb>
Wed, 7 Aug 2013 16:59:40 +0000 (16:59 +0000)
class.

git-svn-id: http://gpsbabel.googlecode.com/svn/trunk@4517 f51c46e8-681c-474f-0cfe-069cfd0219fb

21 files changed:
gpsbabel/an1.cc
gpsbabel/cet_util.cc
gpsbabel/cst.cc
gpsbabel/csv_util.cc
gpsbabel/defs.h
gpsbabel/easygps.cc
gpsbabel/garmin_txt.cc
gpsbabel/gdb.cc
gpsbabel/geo.cc
gpsbabel/gpx.cc
gpsbabel/html.cc
gpsbabel/kml.cc
gpsbabel/lmx.cc
gpsbabel/mmo.cc
gpsbabel/navicache.cc
gpsbabel/shape.cc
gpsbabel/tmpro.cc
gpsbabel/tpo.cc
gpsbabel/unicsv.cc
gpsbabel/vcf.cc
gpsbabel/waypt.cc

index ba5f2e1ebe307046ab30c9c2fe53ec2325a76c7e..d8f65ac6f078ee50eeef29aacde32dd6d4ab25aa 100644 (file)
@@ -710,12 +710,14 @@ static void Read_AN1_Waypoints(gbfile* f)
     wpt_tmp->notes = xstrdup(rec->comment);
     wpt_tmp->description = xstrdup(rec->name);
     if (rec->url) {
-      wpt_tmp->url = xstrdup(rec->url);
+      UrlLink l(rec->url);
+      wpt_tmp->AddUrlLink(l);
     } else if (NULL != (url=strstr(wpt_tmp->description, "{URL="))) {
       *url = '\0';
       url += 5;
       url[strlen(url)-1] = '\0';
-      wpt_tmp->url = xstrdup(url);
+      UrlLink l(url);
+      wpt_tmp->AddUrlLink(l);
     }
 
     if (rec->image_name) {
@@ -778,13 +780,14 @@ Write_One_AN1_Waypoint(const waypoint* wpt)
     xfree(extra);
   }
 
-  if (!nourl && wpt->hasLink()) {
-    int len = 7 + wpt->url.length();
+  if (!nourl && wpt->HasUrlLink()) {
+    UrlLink l = wpt->GetUrlLink();
+    int len = 7 + l.url_.length();
     char* extra = (char*)xmalloc(len);
-    sprintf(extra, "{URL=%s}", wpt->url.toUtf8().data());
+    sprintf(extra, "{URL=%s}", l.url_.toUtf8().data());
     rec->name = xstrappend(rec->name, extra);
     xfree(extra);
-    rec->url = xstrdup(wpt->url.toUtf8().data());
+    rec->url = xstrdup(l.url_.toUtf8().data());
   }
 
   if (wpt->notes) {
index 51ab342bc7b1d7ebfb8637820be6b94f77803802..ee314af76c3b229c1732d9bcd2500ae877293182 100644 (file)
@@ -1035,7 +1035,6 @@ cet_convert_waypt(const waypoint* wpt)
 {
   waypoint* w = (waypoint*)wpt;
   format_specific_data* fs;
-  url_link* url_next;
   geocache_data* gc_data = (geocache_data*)wpt->gc_data;
 
   if ((cet_output == 0) && (w->wpt_flags.cet_converted != 0)) {
@@ -1048,17 +1047,6 @@ cet_convert_waypt(const waypoint* wpt)
   w->description = cet_convert_string(wpt->description);
   w->notes = cet_convert_string(wpt->notes);
 
-  const char*url = cet_convert_string(wpt->url);
-  const char*url_link_text = cet_convert_string(wpt->url_link_text);
-  w->url = url;
-  w->url_link_text = url_link_text;
-  xfree(url);
-  xfree(url_link_text);
-
-  for (url_next = w->url_next; url_next; url_next = url_next->url_next) {
-    url_next->url = cet_convert_string(url_next->url);
-    url_next->url_link_text = cet_convert_string(url_next->url_link_text);
-  }
   if (gc_data) {
     const char *placer = cet_convert_string(gc_data->placer);
     const char *hint = cet_convert_string(gc_data->hint);
index f13f9c9e7cfd97d6c73c5d27def6e25810c58368..1353c31d7f9dc54c1ec8b3b0c6e32dfcc758ff78 100644 (file)
@@ -60,14 +60,10 @@ cst_add_wpt(const route_head* track, waypoint* wpt)
 
   if (wpt->shortname != NULL) {
     waypt_add(waypt_dupe(wpt));
-#if 0
-    if (wpt->url != NULL) {
-      xfree(wpt->url);
-      wpt->url = NULL;
-    }
-#else
-    wpt->url.clear();
-#endif
+   // Rather than creating a new waypt on each read, tis format bizarrely
+   // recycles the same one, relying on waypt_dupe() above and then manually
+   // resetting fields.  Weird.
+   wpt->url_link_list_.clear();
 
     if (temp_route == NULL) {
       temp_route = route_head_alloc();
@@ -220,7 +216,8 @@ cst_data_read(void)
         if (strncmp(cin + 2, "bitmap", 6) == 0) {
           cin = lrtrim(cin + 8);
           if (*cin != '\0') {
-            wpt->url = cst_make_url(cin);
+            UrlLink l(cst_make_url(cin));
+            wpt->AddUrlLink(l);
           }
         }
 
@@ -326,40 +323,6 @@ cst_data_read(void)
   }
 }
 
-#if 0
-static void
-cst_wr_init(const char* fname)
-{
-  fout = gbfopen(fname, "w", MYNAME);
-}
-
-static void
-cst_wr_deinit(void)
-{
-  gbfclose(fout);
-}
-
-static void
-cst_route_hdr(const route_head* rte)
-{
-}
-
-static void
-cst_route_tlr(const route_head* rte)
-{
-}
-
-static void
-cst_write_wpt(const waypoint* wpt)
-{
-}
-
-static void
-cst_data_write(void)
-{
-}
-#endif
-
 ff_vecs_t cst_vecs = {
   ff_type_file,
   { ff_cap_read, ff_cap_read, ff_cap_read },
index 2056a405ed73faec4b98580b5d69373c37ffac55..9c3792e5ace40d627963850f05961675ad984546 100644 (file)
@@ -164,6 +164,7 @@ static int waypt_out_count;
 static route_head* csv_track, *csv_route;
 static double utm_northing, utm_easting, utm_zone = 0;
 static char utm_zonec;
+static UrlLink* link_;
 #endif // CSVFMTS_ENABLED
 
 
@@ -991,10 +992,12 @@ xcsv_parse_val(const char* s, waypoint* wpt, const field_map_t* fmp,
     wpt->notes = csv_stringtrim(s, "", 0);
     break;
   case XT_URL:
-    wpt->url = QString(s).trimmed();
+    if (!link_) link_ = new UrlLink;
+    link_->url_ = QString(s).trimmed();
     break;
   case XT_URL_LINK_TEXT:
-    wpt->url_link_text = QString(s).trimmed();
+    if (!link_) link_ = new UrlLink;
+    link_->url_link_text_ = QString(s).trimmed();
     break;
   case XT_ICON_DESCR:
     wpt->icon_descr = QString(s).trimmed();
@@ -1464,6 +1467,12 @@ xcsv_data_read(void)
                                        DATUM_WGS84);
       }
 
+      if (link_) {
+        wpt_tmp->AddUrlLink(*link_);
+        delete link_;
+        link_ = NULL;
+      }
+
       switch (xcsv_file.datatype) {
       case unknown_gpsdata:
       case wptdata:
@@ -1667,16 +1676,20 @@ xcsv_waypt_pr(const waypoint* wpt)
         strcpy(buff, xcsv_urlbase);
         off = strlen(xcsv_urlbase);
       }
-      if (wpt->hasLink()) {
-        snprintf(buff + off, sizeof(buff) - off, fmp->printfc, wpt->url.toUtf8().data());
+      if (wpt->HasUrlLink()) {
+        UrlLink l = wpt->GetUrlLink();
+        snprintf(buff + off, sizeof(buff) - off, fmp->printfc, l.url_.toUtf8().data());
       } else {
         strcpy(buff, (fmp->val && *fmp->val) ? fmp->val : "\"\"");
       }
     }
     break;
-    case XT_URL_LINK_TEXT:
+    case XT_URL_LINK_TEXT: 
+      if (wpt->HasUrlLink()) {
+      UrlLink l = wpt->GetUrlLink();
       snprintf(buff, sizeof(buff), fmp->printfc,
-               (wpt->hasLinkText()) ? wpt->url_link_text.toUtf8().data() : fmp->val);
+               !l.url_link_text_.isEmpty() ? l.url_link_text_.toUtf8().data() : fmp->val);
+      }
       break;
     case XT_ICON_DESCR:
       writebuff(buff, fmp->printfc,
index cbeb2b10bbf172a96f62ded93594cda14a3085d8..e0eb3cd06637c5680c456b396b0ae3cf6bba47a8 100644 (file)
@@ -36,7 +36,9 @@
 #include "inifile.h"
 #include "session.h"
 
+#include <Qtcore/QString>
 #include <QtCore/QDebug>
+
 # include "src/core/datetime.h"
 
 // Turn on Unicode in expat?
@@ -364,16 +366,22 @@ fs_xml* fs_xml_alloc(long type);
 /*
  * Structures and functions for multiple URLs per waypoint.
  */
-class url_link {
- public:
-    url_link() :
-    url_next(NULL)
-     {} ;
-  url_link* url_next;
-  QString url;
-  QString url_link_text;
+
+class UrlLink {
+ public: 
+   UrlLink() { } 
+   UrlLink(QString url) :
+    url_(url)
+   { }
+   UrlLink(QString url, QString url_link_text) :
+    url_(url),
+    url_link_text_(url_link_text)
+  { }
+  QString url_;
+  QString url_link_text_;
 };
 
+
 /*
  * Misc bitfields inside struct waypoint;
  */
@@ -454,7 +462,6 @@ public:
   shortname(NULL),
   description(NULL),
   notes(NULL),
-  url_next(NULL),
   route_priority(0),
   hdop(0),
   vdop(0),
@@ -516,18 +523,13 @@ public:
    */
   char* notes;
 
-  /* This is a bit icky.   Multiple waypoint support is an
-   * afterthought and I don't want to change our data structures.
-   * So we have the first in the waypoint itself and subsequent
-   * ones in a linked list.
-   * We also use an implicit anonymous union here, so these three
-   * members must match struct url_link...
+  /* TODO: UrlLink should probably move to a "real" class of its own.
    */
-  url_link* url_next;
-  bool hasLink() const {return !url.isEmpty(); }
-  bool hasLinkText() const {return !url_link_text.isEmpty(); }
-  QString url;
-  QString url_link_text;
+  QList<UrlLink> url_link_list_;
+  bool HasUrlLink() const {return !url_link_list_.isEmpty(); }
+  const UrlLink& GetUrlLink() const { return url_link_list_[0]; }
+  const QList<UrlLink> GetUrlLinks() const { return url_link_list_; }
+  void AddUrlLink(const UrlLink l) { url_link_list_.push_back(l); }
 
   wp_flags wpt_flags;
   QString icon_descr;
index f644ccd208795bc18bf4eaba839e517b92b46c7f..cbca78c1b732c66b5c3259b82570c2c551da8ea8 100644 (file)
@@ -84,6 +84,7 @@ data_read(void)
     waypoint* wpt_tmp;
 
     wpt_tmp = waypt_new();
+    UrlLink link;
 
     for (tag = gbfgetc(file_in); tag != 0xff; tag = gbfgetc(file_in)) {
       switch (tag) {
@@ -98,7 +99,7 @@ data_read(void)
         wpt_tmp->notes = gbfgetpstr(file_in);;
         break;
       case 6:
-        wpt_tmp->url_link_text = gbfgetpstr(file_in);;
+        link.url_link_text_ = gbfgetpstr(file_in);;
         break;
       case 7:
         wpt_tmp->icon_descr = gbfgetpstr(file_in);;
@@ -107,10 +108,10 @@ data_read(void)
         wpt_tmp->notes = gbfgetcstr(file_in);
         break;
       case 9: /* NULL Terminated (vs. pascal) link */
-        wpt_tmp->url = gbfgetcstr(file_in);
+        link.url_ = gbfgetcstr(file_in);
         break;
       case 0x10:
-        wpt_tmp->url_link_text = gbfgetcstr(file_in);
+        link.url_link_text_ = gbfgetcstr(file_in);
         break;
       case 0x63:
         wpt_tmp->latitude = gbfgetdbl(file_in);
@@ -134,6 +135,9 @@ data_read(void)
         ;
       }
     }
+    if (!link.url_.isEmpty() || !link.url_link_text_.isEmpty()) {
+       wpt_tmp->AddUrlLink(link);
+    }
     waypt_add(wpt_tmp);
     p = gbfgetc(file_in);
   } while (!gbfeof(file_in) && (p == 'W'));
@@ -167,13 +171,14 @@ ez_disp(const waypoint* wpt)
     gbfputc(5, file_out);
     gbfputpstr(wpt->notes, file_out);
   }
-  if (wpt->hasLinkText()) {
+  UrlLink link = wpt->GetUrlLink();
+  if (!link.url_link_text_.isEmpty()) {
     gbfputc(6, file_out);
-    gbfputpstr(wpt->url_link_text, file_out);
+    gbfputpstr(link.url_link_text_, file_out);
   }
-  if (wpt->hasLink()) {
+  if (!link.url_.isEmpty()) {
     gbfputc(9, file_out);
-    gbfputcstr(wpt->url, file_out);
+    gbfputcstr(link.url_, file_out);
   }
   gbfputc(0xff, file_out);
 }
index efd6b894b0950905c18f3169426e4b1a42eba29f..72349dfbdd381bb09a552bfa63f625b19a1cb731 100644 (file)
@@ -619,7 +619,12 @@ write_waypt(const waypoint* wpt)
   country = gt_get_icao_country(GMSD_GET(cc, ""));
   print_string("%s\t", (country != NULL) ? country : "");
   print_date_and_time(wpt->GetCreationTime(), 0);
-  print_string("%s\t", wpt->hasLink() ? wpt->url : "");
+  if (wpt->HasUrlLink()) {
+    UrlLink l = wpt->GetUrlLink();
+    print_string("%s\t", l.url_);
+  } else {
+    print_string("%s\t", "");
+  }
   print_categories(GMSD_GET(category, 0));
 
   gbfprintf(fout, "\r\n");
@@ -1194,8 +1199,10 @@ parse_waypoint(void)
       wpt->creation_time = ct;
       }
       break;
-    case 17:
-      wpt->url = str;
+    case 17: {
+      UrlLink l(str);
+      wpt->AddUrlLink(l);
+      }
       break;
     case 18:
       GMSD_SET(category, parse_categories(str));
index f3c73b0ef9973fd700a45fedce51abf2687eb60f..0fa4f77d607147ecb5472ddbaa4b101f7caf6b4b 100644 (file)
@@ -631,10 +631,13 @@ read_waypoint(gt_waypt_classes_e* waypt_class_out)
       xfree(temp);
     }
 
-    res->url = FREAD_CSTR_AS_QSTR;
+    QString linky = FREAD_CSTR_AS_QSTR;
+    UrlLink l(linky);
+    if (!linky.isEmpty()) {
+      res->AddUrlLink(l);
+    }
     if (wpt_class != 0) {
-      res->description = xstrdup(res->url.toUtf8().data());
-      res->url.clear();
+      res->description = xstrdup(l.url_.toUtf8().data());
     }
   } else { // if (gdb_ver >= GDB_VER_3)
     int i, url_ct;
@@ -1354,8 +1357,13 @@ write_waypoint(
 
     FWRITE(zbuf, 3);
     FWRITE(zbuf, 4);
+    QString ld;
+    if (wpt->HasUrlLink()) {
+      UrlLink l = wpt->GetUrlLink();
+      ld = l.url_;
+    }
     descr = (wpt_class < gt_waypt_class_map_point) ?
-            wpt->url : wpt->description;
+            ld : wpt->description;
     if ((descr != NULL) && (wpt_class >= gt_waypt_class_map_point) && \
         descr.compare(wpt->shortname) == 0) {
       descr.clear();
@@ -1363,7 +1371,7 @@ write_waypoint(
     FWRITE_CSTR(descr);
   } else { /* if (gdb_ver > GDB_VER_3) */
     int cnt;
-    url_link* url_next;
+//    url_link* url_next;
     const char* str;
 
     if (wpt_class < gt_waypt_class_map_point) {        /* street address */
@@ -1387,21 +1395,11 @@ write_waypoint(
     FWRITE_CSTR(str);                          /* instruction */
 
     cnt = 0;
-    if (wpt->hasLink()) {
-      cnt++;
-    }
-    for (url_next = wpt->url_next; (url_next); url_next = url_next->url_next)
-      if (!url_next->url.isEmpty()) {
-        cnt++;
-      }
+    cnt += wpt->url_link_list_.size();
     FWRITE_i32(cnt);
-    if (wpt->hasLink()) {
-      FWRITE_CSTR(wpt->url);
+    foreach(UrlLink l, wpt->GetUrlLinks()) {
+      FWRITE_CSTR(l.url_.toUtf8().data());
     }
-    for (url_next = wpt->url_next; (url_next); url_next = url_next->url_next)
-      if (!url_next->url.isEmpty()) {
-        FWRITE_CSTR(url_next->url.toUtf8().data());
-      }
   }
 
   FWRITE_i16(GMSD_GET(category, gdb_category));
@@ -1656,9 +1654,16 @@ write_waypoint_cb(const waypoint* refpt)
   rtrim(((waypoint*)refpt)->shortname);
   test = gdb_find_wayptq(&wayptq_out, refpt, 1);
 
+  if (refpt->HasUrlLink() && test && test->HasUrlLink() && route_flag == 0) {
+    UrlLink orig_link = refpt->GetUrlLink();
+    UrlLink test_link = test->GetUrlLink();
+    if (orig_link.url_ != test_link.url_) {
+      test = NULL;
+    }
+  }
+
   if ((test != NULL) && (route_flag == 0)) {
-    if ((str_not_equal(test->notes, refpt->notes)) ||
-        test->url.compare(refpt->url)) {
+    if (str_not_equal(test->notes, refpt->notes)) {
       test = NULL;
     }
   }
index 6a89922989c3d865cb5bb9096e91bbca415e1f99..302b47a309d34a369312f9e1f1ccc76728259508 100644 (file)
@@ -87,8 +87,8 @@ void GeoReadLoc()
         wpt->icon_descr = reader.readElementText();
       } else if (tag_name == "link") {
         QXmlStreamAttributes a = reader.attributes();
-        wpt->url_link_text = a.value("text").toString();
-        wpt->url = reader.readElementText();
+        waypt_add_url(wpt, 
+                      reader.readElementText(), a.value("text").toString());
       } else if (tag_name == "difficulty") {
         wpt->gc_data->diff = reader.readElementText().toInt() * 10;
       } else if (tag_name == "terrain") {
@@ -207,10 +207,11 @@ geo_waypt_pr(const waypoint* waypointp)
 
   writer.writeTextElement("type", deficon ? deficon : waypointp->icon_descr);
 
-  if (waypointp->hasLink()) {
+  if (waypointp->HasUrlLink()) {
     writer.writeStartElement("link");
     writer.writeAttribute("text ", "Cache Details");
-    writer.writeCharacters(waypointp->url);
+    UrlLink link = waypointp->GetUrlLink();
+    writer.writeCharacters(link.url_);
     writer.writeEndElement();
   }
 
index 5d1d601dfbc75d7b506a7cad112a19678e720e17..b60cfa8be7673cbec52fbeec7452c7ff154c73f1 100644 (file)
@@ -52,6 +52,7 @@ static char* gpx_author = NULL;
 static QString current_tag;
 
 static waypoint* wpt_tmp;
+static UrlLink* link_;
 static int cache_descr_is_html;
 static gbfile* fd;
 static const char* input_fname;
@@ -498,6 +499,7 @@ tag_wpt(const char** attrv)
   const char** avp = &attrv[0];
 
   wpt_tmp = waypt_new();
+  link_ = new UrlLink;
 
   cur_tag = NULL;
   while (*avp) {
@@ -963,6 +965,11 @@ gpx_end(void* data, const XML_Char* xml_el)
      * Waypoint-specific tags.
      */
   case tt_wpt:
+    if (link_ && !link_->url_.isEmpty()) {
+      wpt_tmp->AddUrlLink(*link_);
+      delete link_;
+      link_ = NULL;
+    }
     waypt_add(wpt_tmp);
     logpoint_ct = 0;
     cur_tag = NULL;
@@ -1178,12 +1185,12 @@ gpx_end(void* data, const XML_Char* xml_el)
   case tt_wpt_url:
   case tt_trk_trkseg_trkpt_url:
   case tt_rte_rtept_url:
-    wpt_tmp->url = cdatastrp;
+    link_->url_ = cdatastrp;
     break;
   case tt_wpt_urlname:
   case tt_trk_trkseg_trkpt_urlname:
   case tt_rte_rtept_urlname:
-    wpt_tmp->url_link_text = cdatastrp;
+    link_->url_link_text_ = cdatastrp;
     break;
   case tt_wpt_link:
 //TODO: implement GPX 1.1      case tt_trk_trkseg_trkpt_link:
@@ -1194,7 +1201,7 @@ gpx_end(void* data, const XML_Char* xml_el)
       lt = xstrdup(lrtrim(link_text));
     }
 
-    waypt_add_url(wpt_tmp, xstrdup(link_url), lt);
+    waypt_add_url(wpt_tmp, link_url, lt);
     link_text = NULL;
   }
   break;
@@ -1484,22 +1491,22 @@ void free_gpx_extras(xml_tag* tag)
 static void
 write_gpx_url(const waypoint* waypointp)
 {
-  if (waypointp->url == NULL) {
+  if (!waypointp->HasUrlLink()) {
     return;
   }
 
   if (gpx_wversion_num > 10) {
-    url_link* tail;
-    for (tail = (url_link*)&waypointp->url_next; tail; tail = tail->url_next) {
+    foreach(UrlLink l, waypointp->GetUrlLinks()) {
       writer.writeStartElement("link");
-      writer.writeAttribute("href", tail->url);
-      writer.writeOptionalTextElement("text", tail->url_link_text);
+      writer.writeAttribute("href", l.url_);
+      writer.writeOptionalTextElement("text", l.url_link_text_);
       writer.writeEndElement();
     }
     return;
   }
-  writer.writeTextElement("url", QString(urlbase) + QString(waypointp->url));
-  writer.writeOptionalTextElement("urlname", QString(waypointp->url_link_text));
+  UrlLink l = waypointp->GetUrlLink();
+  writer.writeTextElement("url", QString(urlbase) + QString(l.url_));
+  writer.writeOptionalTextElement("urlname", QString(l.url_link_text_));
 }
 
 /*
index 9f1e8b79f88b59db7fb1d7e8e98d2b42faf113d2..85583ee738420240cda0d365cdfd72348d534620 100644 (file)
@@ -108,9 +108,10 @@ html_disp(const waypoint* wpt)
   }
   gbfprintf(file_out, "<br>\n");
   if (strcmp(wpt->description, wpt->shortname)) {
-    if (wpt->hasLink()) {
+    if (wpt->HasUrlLink()) {
       char* d = html_entitize(wpt->description);
-      gbfprintf(file_out, "<a href=\"%s\">%s</a>", wpt->url.toUtf8().data(), d);
+      UrlLink link = wpt->GetUrlLink();
+      gbfprintf(file_out, "<a href=\"%s\">%s</a>", link.url_.toUtf8().data(), d);
       xfree(d);
     } else {
       gbfprintf(file_out, "%s", wpt->description);
index 9592e63db06440d858bb59da2b9f69302592bedb..05fb0d07cf4479eb1328e5cf13d9ac1dd01a2bad 100644 (file)
@@ -1437,8 +1437,11 @@ static void kml_geocache_pr(const waypoint* waypointp)
 
   writer->writeStartElement("name");
   writer->writeCharacters("\n"); // FIXME  forced formatting to match old references
-  writer->writeCDATA(waypointp->url_link_text);
-  writer->writeCharacters("\n"); // FIXME  forced formatting to match old references
+  if (waypointp->HasUrlLink()) {
+    UrlLink link = waypointp->GetUrlLink();
+    writer->writeCDATA(link.url_link_text_);
+    writer->writeCharacters("\n"); // FIXME  forced formatting to match old references
+  }
   writer->writeEndElement(); // Close name tag
 
   // Timestamp
@@ -1466,8 +1469,9 @@ static void kml_geocache_pr(const waypoint* waypointp)
     kml_write_data_element("gc_num", waypointp->shortname);
   }
 
-  if (waypointp->hasLinkText()) {
-    kml_write_data_element("gc_name", waypointp->url_link_text);
+  if (waypointp->HasUrlLink()) {
+    UrlLink link = waypointp->GetUrlLink();
+    kml_write_data_element("gc_name", link.url_link_text_);
   }
 
   if (!waypointp->gc_data->placer.isEmpty()) {
@@ -1542,16 +1546,17 @@ static void kml_waypt_pr(const waypoint* waypointp)
   writer->writeOptionalTextElement("name", waypointp->shortname);
 
   // Description
-  if (waypointp->hasLink()) {
+  if (waypointp->HasUrlLink()) {
     writer->writeEmptyElement("snippet");
-    if (waypointp->hasLinkText()) {
-      QString odesc = waypointp->url;
-      QString olink = waypointp->url_link_text;
+    UrlLink link = waypointp->GetUrlLink();
+    if (!link.url_link_text_.isEmpty()) {
+      QString odesc = link.url_;
+      QString olink = link.url_link_text_;
       writer->writeStartElement("description");
       writer->writeCDATA(QString("<a href=\"%1\">%2</a>").arg(odesc, olink));
       writer->writeEndElement(); // Close description tag
     } else {
-      writer->writeTextElement("description", waypointp->url);
+      writer->writeTextElement("description", link.url_);
     }
   } else {
     if (strcmp(waypointp->shortname, waypointp->description)) {
index 50c829ec45a2b33f091de945442d1f60ede4ad77..9b0e83fbca814c2e8c76b5b898848f87090e4dec 100644 (file)
@@ -240,15 +240,16 @@ lmx_print(const waypoint* wpt)
   }
   lmx_end_tag(0x4A, 3); // coordinates
 
-  if (wpt->hasLink()) {
+  if (wpt->HasUrlLink()) {
     lmx_start_tag(0x65, 3); // mediaLink
     if (!binary) {
       gbfputc('\n', ofd);
     }
-    if (wpt->hasLinkText()) {
-      lmx_write_xml(0x48, wpt->url_link_text, 4);  // name
+    UrlLink link = wpt->GetUrlLink();
+    if (!link.url_link_text_.isEmpty()) {
+      lmx_write_xml(0x48, link.url_link_text_, 4);  // name
     }
-    lmx_write_xml(0x67, wpt->url, 4); // url
+    lmx_write_xml(0x67, link.url_, 4); // url
     lmx_end_tag(0x65, 3); // mediaLink
   }
 
index 317d289e300c1c9a6fbce2d5d27875837211a026..c9fff165595d359003cc4891eb32bd301b8f3525 100644 (file)
@@ -515,7 +515,8 @@ mmo_read_CObjWaypoint(mmo_data_t* data)
 
     cx = lrtrim(xstrndup(cx, cend - cx));
     if (*cx) {
-      wpt->url = cx;
+      UrlLink l(cx);
+      wpt->AddUrlLink(l);
     } else {
       xfree(cx);
     }
@@ -524,7 +525,7 @@ mmo_read_CObjWaypoint(mmo_data_t* data)
       wpt->notes = xstrdup(cend);
     }
 
-    if (wpt->hasLink()) {
+    if (wpt->HasUrlLink()) {
       DBG((sobj, "url = \"%s\"\n", wpt->url));
     }
   } else if (*str) {
@@ -985,8 +986,9 @@ mmo_finalize_rtept_cb(const waypoint* wptref)
     if (wpt2->notes) {
       wpt->notes = xstrdup(wpt2->notes);
     }
-    if (wpt2->hasLink()) {
-      wpt->notes = xstrdup(wpt2->url.toUtf8().data());
+    if (wpt2->HasUrlLink()) {
+      UrlLink l = wpt2->GetUrlLink();
+      wpt->notes = xstrdup(l.url_.toUtf8().data());
     }
 
     wpt->proximity = wpt2->proximity;
@@ -1276,9 +1278,10 @@ mmo_write_wpt_cb(const waypoint* wpt)
     gbfputuint16(0, fout);  /* extra bytes */
   }
 
-  if (wpt->hasLink()) {
+  if (wpt->HasUrlLink()) {
     str = xstrdup("_FILE_ ");
-    str = xstrappend(str, wpt->url.toUtf8().data());
+    UrlLink l = wpt->GetUrlLink();
+    str = xstrappend(str, l.url_.toUtf8().data());
     str = xstrappend(str, "\n");
   } else {
     str = xstrdup("");
index 3bf337a99605e5f400bd2f404afade862a3dbc94..f9d25cea572f7235034de2f1e2913dfd8545c702 100644 (file)
@@ -129,7 +129,8 @@ nav_start(void* data, const XML_Char* xml_el, const XML_Char** xml_attr)
 
         id = atoi(ap[1]);
         xasprintf(&wpt_tmp->shortname, "N%05X", id);
-        wpt_tmp->url = QString(NC_URL) + QString::number(id);
+        UrlLink l(QString(NC_URL) + QString::number(id));
+        wpt_tmp->AddUrlLink(l);
       } else if (0 == strcmp(ap[0], "name")) {
         wpt_tmp->description = xstrdup(ap[1]);
       } else if (0 == strcmp(ap[0], "user_name")) {
index 1e233d07475cf79cd0ffb3274315e79339c68cc6..0ae8ff3b403cc628bfa62dfe3bdb5d3133fcc516 100644 (file)
@@ -187,7 +187,8 @@ my_read(void)
       wpt->longitude = shp->dfXMin;
       wpt->shortname = xstrdup(name);
       if (url) {
-        wpt->url = xstrdup(url);
+        UrlLink l(url);
+        wpt->AddUrlLink(l);
       }
       waypt_add(wpt);
       break;
index 754e4ccb2eb915f2fd3b8481a58b9fcc2c1de78d..0cc89866ef06af6a43c26badcde3a5a56b7fa467 100644 (file)
@@ -143,7 +143,8 @@ data_read(void)
           */
           holder = csv_stringtrim(s, "", 0);
           if (strstr(holder, "http:") != NULL) {
-            wpt_tmp->url = holder;
+            UrlLink link(holder);
+            wpt_tmp->AddUrlLink(link);
           }
           xfree(holder);
           break;
@@ -211,6 +212,13 @@ tmpro_waypt_pr(const waypoint * wpt)
   /* Number of characters */
   /*  25    6      80         8    8      8         8       8    4       4       128      */
 
+  const char *l;
+  if (wpt->HasUrlLink()) {
+    UrlLink link = wpt->GetUrlLink();
+    l  = link.url_.toUtf8().data();
+  } else {
+    l = "";
+  }
   gbfprintf(file_out, "new\t%.6s\t%.80s\t%08.6f\t%08.6f\t\t\t%.2f\t%d\t%d\t%.128s\n",
             shortname,
             description,
@@ -219,7 +227,7 @@ tmpro_waypt_pr(const waypoint * wpt)
             wpt->altitude,
             colour,
             icon,
-            wpt->hasLink() ? wpt->url.toUtf8().data() : ""
+            l
            );
 
 
index ae05acb2d69b34dd7d3d51ef67c9e2bf6b2cc568..8700de1806d5b1f226b23ca53f03ee5c5bd1e29f 100644 (file)
@@ -1035,7 +1035,8 @@ void tpo_process_map_notes(void)
       notes[0] = '\0';
       gbfread(notes, 1, name_length, tpo_file_in);
       notes[name_length] = '\0';  // Terminator
-      waypoint_temp->url = notes;
+      UrlLink l(notes);
+      waypoint_temp->AddUrlLink(l);
 //printf("Notes: %s\n", notes);
       xfree(notes);
     }
@@ -1051,7 +1052,8 @@ void tpo_process_map_notes(void)
       notes[0] = '\0';
       gbfread(notes, 1, name_length, tpo_file_in);
       notes[name_length] = '\0';  // Terminator
-      waypoint_temp->url = notes;
+      UrlLink l(notes);
+      waypoint_temp->AddUrlLink(l);
 //printf("Notes: %s\n", notes);
       xfree(notes);
     }
index ce2b4e9d4ab60f8f5665dab7fcf9c6029d70e5b4..4ae326bef02622b35f3ddc2629a2633490e51139 100644 (file)
@@ -744,8 +744,11 @@ unicsv_parse_one_line(char *ibuf)
       wpt->notes = xstrdup(s);
       break;
 
-    case fld_url:
-      wpt->url = xstrdup(s);
+    case fld_url: {
+qDebug() << s;
+      UrlLink l(s);
+      wpt->AddUrlLink(l);
+      } 
       break;
 
     case fld_altitude:
@@ -1365,7 +1368,7 @@ unicsv_waypt_enum_cb(const waypoint *wpt)
       gb_setbit(&unicsv_outp_flags, fld_notes);
     }
   }
-  if (wpt->hasLink()) {
+  if (wpt->HasUrlLink()) {
     gb_setbit(&unicsv_outp_flags, fld_url);
   }
   if (wpt->creation_time.isValid()) {
@@ -1777,8 +1780,13 @@ unicsv_waypt_disp_cb(const waypoint *wpt)
       gbfputs(unicsv_fieldsep, fout);
     }
   }
-  if FIELD_USED(fld_url) {
-    unicsv_print_str(wpt->url);
+  if (FIELD_USED(fld_url)) {
+    if (!wpt->HasUrlLink()) {
+      unicsv_print_str("");
+    } else {
+      UrlLink l = wpt->GetUrlLink();
+      unicsv_print_str(l.url_);
+    }
   }
 
   if FIELD_USED(fld_garmin_facility) {
index 1070bba5a5b67fb9be1225585d3319a61bd2ec45..65ab611ac3238585c430eaec4a20cdf4cb5fca54 100644 (file)
@@ -106,8 +106,9 @@ vcf_disp(const waypoint *wpt)
   gbfprintf(file_out, "N:%s;%s;;;\n", wpt->description,wpt->shortname);
   gbfprintf(file_out, "ADR:%c%d %06.3f %c%d %06.3f\n", wpt->latitude < 0 ? 'S' : 'N',  abs(latint), 60.0 * (fabs(wpt->latitude) - latint), wpt->longitude < 0 ? 'W' : 'E', abs(lonint), 60.0 * (fabs(wpt->longitude) - lonint));
 
-  if (wpt->hasLink()) {
-    gbfprintf(file_out, "URL:%s\n", wpt->url.toUtf8().data());
+  if (wpt->HasUrlLink()) {
+    UrlLink link = wpt->GetUrlLink();
+    gbfprintf(file_out, "URL:%s\n", link.url_.toUtf8().data());
   }
 
   gbfprintf(file_out, "NOTE:");
index 6dc9c8b6921db77807aecb7cb1fd805439eac56e..76f44cc442c9ebd7f18197f00ddfdcbe550db5d0 100644 (file)
@@ -68,13 +68,6 @@ waypt_dupe(const waypoint *wpt)
     tmp->notes = xstrdup(wpt->notes);
   }
 
-  tmp->url = (wpt->url);
-  tmp->url_link_text = wpt->url_link_text;
-
-  for (url_link* url_next = wpt->url_next; url_next; url_next = url_next->url_next) {
-    waypt_add_url(tmp, url_next->url, url_next->url_link_text);
-  }
-
   tmp->icon_descr = wpt->icon_descr;
 
   if (wpt->gc_data != &empty_gc_data) {
@@ -481,32 +474,7 @@ waypt_restore(signed int count, queue *head_bak)
 void
 waypt_add_url(waypoint *wpt, const QString& link, const QString& url_link_text)
 {
-  if ((link == NULL) && (url_link_text == NULL)) {
-    return;
-  }
-
-  /* Special case first one; it goes right into the waypoint. */
-  if ((wpt->url == NULL)  && (wpt->url_link_text == NULL)) {
-    wpt->url = link;
-    wpt->url_link_text = url_link_text;
-  } else {
-    url_link *tail;
-    url_link *new_link = new url_link;
-    new_link->url = link;
-    new_link->url_link_text = url_link_text;
-
-    /* Find current end of chain and tack this onto the end.. */
-    for (tail = wpt->url_next;; tail = tail->url_next) {
-      if (tail == NULL) {
-        wpt->url_next = new_link;
-        break;
-      }
-      if (tail->url_next == NULL) {
-        tail->url_next = new_link;
-        break;
-      }
-    }
-  }
+  wpt->url_link_list_.push_back(UrlLink(link, url_link_text));
 }
 
 double